﻿#region File Header

/* File Name    : FacebookQuery.cs
 * Description  : This class represents the Facebook query to be executed
 * Log
 * Date             Author              Description
 * 16-Oct-2011      Robin Jome          Created the class
 * 17-Oct-2011      Robin Jome          Renamed Property Base to BaseUrl
 *                                      Added new query parameters.
 *                                      Removed Parameters property
 *                                      Added method GetUrl() and removed ToString() overload.
 */

#endregion

#region Namespaces

using System;
using System.Collections.Generic;
using System.Configuration;
using System.Text;

#endregion

namespace FacebookAPI.FacebookProperties
{
    #region Class

    /// <summary>
    /// This class represents the Facebook query to be executed
    /// </summary>
    internal class FacebookUrl
    {
        #region Constructors

        /// <summary>
        /// Represents the Facebook query to be executed.
        /// </summary>
        public FacebookUrl()
        {
            this.Fields = new FacebookQueryField();
            this.SearchOptions = new SearchOptions();
            this.OtherParameters = new List<string>();
        }

        #endregion

        #region Properties

        /// <summary>
        /// Gets or sets the value of BaseUrl
        /// </summary>
        /// <value>Represents the base Uri for Graph API calls</value>
        internal string BaseUrl { get { return ConfigurationManager.AppSettings["GraphBaseUrl"].ToString(); } }

        /// <summary>
        /// Gets or sets the value of ObjectId
        /// </summary>
        /// <value>Represents the Id of the Facebook object</value>
        public string ObjectId { get; set; }

        /// <summary>
        /// Gets or sets the value of ConnectionType
        /// </summary>
        /// <value>Represents the Facebook connection</value>
        public Nullable<FacebookConnections> ConnectionType { get; set; }

        /// <summary>
        /// Gets or sets the value of Fields
        /// </summary>
        /// <value>Represents the optional list of Facebook fields to be used.</value>
        public FacebookQueryField Fields { get; set; }

        /// <summary>
        /// Gets or sets the value of AccessToken
        /// </summary>
        /// <value>Gets or sets the value of Facebook access token</value>
        public string AccessToken { get; set; }

        /// <summary>
        /// Gets or sets the value of SearchOptions
        /// </summary>
        public SearchOptions SearchOptions { get; set; }

        /// <summary>
        /// Gets or sets the value of IsIntrospection
        /// </summary>
        /// <value>If set true returns introspection of the object. By default value is false.</value>
        public bool IsIntrospection { get; set; }

        /// <summary>
        /// Gets or sets the value of OtherParameters
        /// </summary>
        /// <value>The list of additional parameters to be used to execute the request.</value>
        public List<string> OtherParameters { get; set; }

        #endregion

        #region Methods

        /// <summary>
        /// Returns the Facebook query string
        /// </summary>
        /// <returns>Returns a Facebook query string</returns>
        public Uri GetUrl()
        {
            #region Prepare parameters

            List<string> parameters = new List<string>();
            if (Fields != null && !string.IsNullOrEmpty(Fields.FieldName) && Fields.FieldValues != null && Fields.FieldValues.Count > 0)
            {
                parameters.Add(Fields.FieldName + "=" + string.Join(",", Fields.FieldValues));
            }
            if (SearchOptions != null)
            {
                if (!string.IsNullOrEmpty(SearchOptions.SearchParameter))
                {
                    parameters.Add("q=" + SearchOptions.SearchParameter);
                }
                if (!string.IsNullOrEmpty(SearchOptions.SearchObjectType))
                {
                    parameters.Add("type=" + SearchOptions.SearchObjectType);
                }
                if (SearchOptions.Limit != null)
                {
                    parameters.Add("limit=" + SearchOptions.Limit.Value.ToString());
                }
                if (SearchOptions.Offset != null)
                {
                    parameters.Add("offset=" + SearchOptions.Offset.Value.ToString());
                }
                if (!string.IsNullOrEmpty(SearchOptions.Until))
                {
                    parameters.Add("until=" + SearchOptions.Until);
                }
                if (!string.IsNullOrEmpty(SearchOptions.Since))
                {
                    parameters.Add("since=" + SearchOptions.Since);
                }
            }
            if (IsIntrospection)
            {
                parameters.Add("metadata=1");
            }
            if (!string.IsNullOrEmpty(AccessToken))
            {
                parameters.Add("access_token=" + AccessToken);
            }
            if (OtherParameters != null)
            {
                parameters.AddRange(OtherParameters.ToArray());
            }

            #endregion

            StringBuilder queryString = new StringBuilder();
            queryString.Append(BaseUrl);
            if (!string.IsNullOrEmpty(ObjectId))
            {
                queryString.Append("/").Append(ObjectId);
            }
            if (ConnectionType != null)
            {
                queryString.Append("/").Append(Enum.GetName(typeof(FacebookConnections), ConnectionType));
            }
            if (parameters.Count > 0)
            {
                queryString.Append("?").Append(string.Join("&", parameters));
            }

            return new Uri(queryString.ToString());
        }

        #endregion
    }

    #endregion
}
